/**
 * com.chaeron.GPS - An API for access to GPS devices.
*
*
* Copyright (c) 2001, 2002 Chaeron Corporation,
* All rights reserved.
* 
* Chaeron grants you a non-exclusive license to use, modify and re-distribute
* this program under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version, provided that this copyright notice and 
* license appear on all copies of the software.
* 
* Software is provided "AS IS," without a warranty of any kind. ALL EXPRESS OR
* IMPLIED REPRESENTATIONS AND WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE
* HEREBY EXCLUDED. THE ENTIRE RISK ARISING OUT OF USING THE SOFTWARE IS ASSUMED
* BY THE LICENSEE. See the GNU General Public License for more details.
*
* CHAERON AND ITS LICENSORS SHALL NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY
* LICENSEE OR ANY THIRD PARTY AS A RESULT OF USING OR DISTRIBUTING SOFTWARE.
* IN NO EVENT WILL CHAERON OR ITS LICENSORS BE LIABLE FOR ANY LOST REVENUE,
* PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL
* OR PUNITIVE DAMAGES, HOWEVER CAUSED AN REGARDLESS OF THE THEORY OF LIABILITY,
* ARISING OUT OF THE USE OF OR INABILITY TO USE SOFTWARE, EVEN IF CHAERON HAS
* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. 
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.

* @version     1.02
* @author      Andrzej Jan Taramina, Chaeron Corporation
*              andrzej@chaeron.com
*/

package com.chaeron.GPS.Garmin;

//***************************************************************************
//*
//*     Imports
//*
//***************************************************************************/

import com.chaeron.GPS.*;
import com.chaeron.GPS.event.*;
import com.chaeron.GPS.exception.*;


//***************************************************************************
//*
//*     ProtocolArrayGarminPacket Class definition
//*
//***************************************************************************/

/**
 * The ProtocolArrayGarminPacket class represents ProductArray Packets
*
*/

public class ProtocolArrayGarminPacket extends GarminPacket
{
	//***************************************************************************
	//*
	//*     Constant definitions
	//*
	//***************************************************************************/
	
	//***************************************************************************
	//*
	//*     Attributes
	//*
	//***************************************************************************/
	
	private int					protocolEntries	= 0;
	private char[]				protocolTags	= null;
	private short[]				protocol	= null;
	
	
	//***************************************************************************
	//*
	//*     Constructors
	//*
	//***************************************************************************/
	
	/**
	 * Create a ProtocolArrayGarminPacket from the given packet data
	*
	* @param	packet		packet data buffer
	* @param	len			length of packet data
	*/
	
	ProtocolArrayGarminPacket( byte[] packet, int len )
	{  
		super( packet, len );
	}
	
	
	//***************************************************************************
	//*
	//*     decode method
	//*
	//***************************************************************************/
	
	/**
	 * Decode the data fields.
	*
	* @throws GPSPacketException
	* @throws GPSFunctionUnavailableException
	*/
	
	public void parseData()  throws GPSPacketException, GPSFunctionUnavailableException
	{  
		if( getPacketIDByte() != Protocol.GARMIN_PID_PROTOCOL_ARRAY ) {
			throw( new GPSPacketException( GPSPacketException.EXCEPTION_PACKETID_INVALID ) );
		} else {
			parseProtocol();
		}
	}
	
	
	/**
	 * Parse out the protocol data
	*/
	
	private void parseProtocol()
	{  
		int				i;
		int				entry = 0;
		byte			chr;
		
		protocolEntries = getDataLength() / 3;
		
		protocolTags = new char[ protocolEntries ];
		protocol = new short[ protocolEntries ];
		
		for( i = 0; i < getDataLength(); i = i + 3 ) {
			chr = getDataByte( i );
			if( chr != GarminGPSImpl.END_PACKET2 ) {
				protocolTags[ entry ] = (char)getDataByte( i );
				protocol[ entry ] = getGarminInt( i + 1 );
				entry++;
			} else {
				protocolEntries--;
			}
		}
	}
	
	
	//***************************************************************************
	//*
	//*     Packet Processing Methods (overriden by subclasses)
	//*
	//***************************************************************************/
	
	/**
	 * Process the packet
	*
	* @param	gps			the GPS object that requested the packet to be processed
	*/
	
	void process( GPS gps )
	{
		if( !isParsed() ) {
			try {
				parse();
				gps.processCapabilitiesPacket( this );
				gps.postGPSEvent( new GPSEvent( GPSEvent.GPS_EVENT_CAPABILITIES, null ) );
			}
			catch( GPSException exception ) {
				gps.postGPSEvent( new GPSEvent( GPSEvent.GPS_EVENT_ERROR, toString(), exception ) );
			}
		}
	}
	
	/**
	 * Get events generated.
	*
	* @return		return a valid event type(s) that will be generated by this packet
	*/
	
	static int getEventsGenerated()
	{  
		return( GPSEvent.GPS_EVENT_ERROR | GPSEvent.GPS_EVENT_CAPABILITIES );
	}
	
	
	//***************************************************************************
	//*
	//*    Accessor methods
	//*
	//***************************************************************************/
	
	/**
	 * Get the number of protocols
	*
	* @return		# of protocols
	*/
	
	public int getProtocolCount()
	{  
		return( protocolEntries );
	}
	
	
	/**
	 * Get the a specific protocol tag
	*
	* @return		protocol tag
	*/
	
	public char getProtocolTag( int index )
	{  
		return( protocolTags[ index ] );
	}
	
	
	/**
	 * Get the a specific protocol data
	*
	* @return		protocol data
	*/
	
	public short getProtocol( int index )
	{  
		return( protocol[ index ] );
	}
	
	
}
